

%{
#include <string>
#include <string.h>
#include <iostream>
#include <cffformat.h>
#ifdef CC_WIN32
#include <cffparser.cpp.h>
#else
#include <cffparser.hpp>
#endif
int yyerror(const char *s);
char* cut_quotes (const char* buffer);
char* cut_escapes (const char* buffer);
extern int yylineno;
%}

%option noyywrap

digit       [0-9]
letters     [a-zA-Z]
letters_us  [_a-zA-Z]
slash		[/]
dot			[\.]
plus_minus	[\-+]
escaped  (\\.)

identifier  {letters_us}+({letters_us}|{digit})*
complex_id	{plus_minus}?({letters_us}|{digit}|{dot}|{escaped}|{slash})*
string_const	\"(\\.|[^\\"])*\"
int_const   {digit}+
float_const {digit}*\.{digit}+



%%
"{"								{ return BLOCK_OPEN; }
"}"								{ return BLOCK_CLOSE; }
"<"								{ return ARROW_OPEN; }
">"								{ return ARROW_CLOSE; }
";"								{ return SEMICOLON; }
":"								{ return COLON; }
"="								{ return ASSIGN; }
{identifier}					{ yylval.lexVal.text = strdup (yytext); return IDENTIFIER; }
{complex_id}					{ yylval.lexVal.text = cut_escapes (yytext); return COMPLEX_IDENTIFIER; }
{string_const}					{ yylval.lexVal.text = cut_quotes (yytext); return STRING_CONST; }
[ \t]*							{}
[\n]							{ ++yylineno; }
.								{ std::cerr << "SCANNER "; yyerror(""); exit(1);	}


%%
/*
{int_const}						{ yylval.lexVal.text = strdup (yytext); return INT_CONST; }
{float_const}					{ yylval.lexVal.text = strdup (yytext); return FLOAT_CONST; }
*/
char* cut_quotes (const char* buffer)
{
	int len = strlen(buffer);
	char* dst = (char*)malloc (len * sizeof(char));
	char* ptr = dst;
	for (unsigned i=1; i<len-1; ++i)
	{
		if (buffer[i] == '\\' && i < len-2)
		{
			*ptr++ = buffer[i+1];
			++i;
		}
		else
		{
			*ptr++ = buffer[i];
		}
	}
	*ptr = '\0';
	return dst;
}


char* cut_escapes (const char* buffer)
{
	int len = strlen(buffer);
	if (len <= 0)
		{
			return strdup (buffer);
		}
	char* dst = (char*)malloc ((len+1) * sizeof(char));
	char* ptr = dst;
	for (unsigned i=0; i<len; ++i)
	{
		if (buffer[i] == '\\' && i < len-1)
		{
			*ptr++ = buffer[i+1];
			++i;
		}
		else
		{
			*ptr++ = buffer[i];
		}
	}
	*ptr = (char)0;
	return dst;
}
